package com.wzdigit.wms.wms.service.inv.count.util;

import cn.hutool.core.collection.CollectionUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.wzdigit.framework.Shift;
import com.wzdigit.wms.basic.domain.basic.Location;
import com.wzdigit.wms.basic.domain.basic.Sku;
import com.wzdigit.wms.basic.domain.basic.SkuCate;
import com.wzdigit.wms.basic.domain.basic.Zone;
import com.wzdigit.wms.basic.domain.inventory.Lotno;
import com.wzdigit.wms.basic.mapper.core.basic.LocationMapper;
import com.wzdigit.wms.basic.mapper.core.basic.SkuMapper;
import com.wzdigit.wms.wms.client.response.inv.count.dto.InvScopeDto;
import com.wzdigit.wms.wms.domain.inv.count.InvCountDtl;
import com.wzdigit.wms.wms.domain.inv.count.InvCountScope;
import com.wzdigit.wms.wms.mapper.inv.count.InvCountDtlMapper;
import com.wzdigit.wms.wms.mapper.inv.count.InvCountHeaderMapper;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

/**
 *  *号重置工具类
 * Created by zyf on 2021/10/11 19:30
 */
@Slf4j
@Service
public class InvStarUtil {
    private static final String STAR="*";

    @Autowired
    private InvCountHeaderMapper invCountHeaderMapper;
    @Autowired
    private InvCountDtlMapper invCountDtlMapper;
    @Autowired
    private LocationMapper locationMapper;
    @Autowired
    private SkuMapper skuMapper;

    public List<String> getZones(List<String> zoneCodes,Integer whsId,Boolean emptyFlag) throws Exception{
            if (CollectionUtil.isEmpty(zoneCodes)){
                return zoneCodes;
            }
            if (!STAR.equals(zoneCodes.get(0))){
                return zoneCodes;
            }
            return invCountHeaderMapper.selectCoutnZones(whsId,null,null,emptyFlag).
                    stream().map(t -> t.getZoneCode()).collect(Collectors.toList());

    }

    public List<String> getLoc(List<String> zoneCodes,List<String> locCodes,Boolean emptyFlag) throws Exception{
            if (CollectionUtil.isEmpty(locCodes)){
                return locCodes;
            }
            if (!STAR.equals(locCodes.get(0))){
                return locCodes;
            }
            return invCountHeaderMapper.selectCoutnLocs(zoneCodes,null,null,emptyFlag).
                    stream().map(t -> t.getLocCode()).collect(Collectors.toList());

    }

    public List<String> getLotno(Integer whsId,List<String> locCodes,List<String> lotnos,Boolean emptyFlag,Boolean putFlag){
        if (CollectionUtil.isEmpty(lotnos)){
            return lotnos;
        }
        if (!STAR.equals(lotnos.get(0))){
            return lotnos;
        }
        List<Lotno> returnLotnoList = invCountHeaderMapper.selectCoutnLotnos(whsId, locCodes, null, null, emptyFlag, putFlag);

        List<String> returnLotnos=new ArrayList<>();
        for (Lotno lotno : returnLotnoList) {
            if (lotno==null){
                continue;
            }
            if (lotno.getLotno()!=null){
                returnLotnos.add(lotno.getLotno());
            }
        }
        return returnLotnos;
    }

    public List<String> getCate(Integer whsId,List<String> locCodes,List<String> lotnos,List<String> cateCodes,
                                Boolean emptyFlag,Boolean putFlag){
        if (!STAR.equals(cateCodes.get(0))){
            return cateCodes;
        }
        return invCountHeaderMapper.selectCoutnCates(whsId,locCodes,lotnos,null,null,emptyFlag,putFlag).
                stream().map(t -> t.getSkuCateCode()).collect(Collectors.toList());
    }

    public List<String> getSku(Integer whsId,List<String> locCodes,List<String> lotnos,List<String> cateCodes,
                               List<String> skuCodes,Boolean emptyFlag,Boolean putFlag){
        if (!STAR.equals(skuCodes.get(0))){
            return skuCodes;
        }
        return invCountHeaderMapper.selectCoutnSku(whsId,locCodes,lotnos,cateCodes,null,null,emptyFlag,putFlag).
                stream().map(t -> t.getSkuCode()).collect(Collectors.toList());
    }


    //查询复盘任务的最父级盘点任务
    public InvCountDtl searchFaterDtl(BigDecimal countDtlId) {
        //查询盘点任务信息
        InvCountDtl countDtl = invCountDtlMapper.
                selectOne(new QueryWrapper<InvCountDtl>().eq("INV_COUNT_DTL_ID", countDtlId));
        if (countDtl==null){
            return null;
        }
        if (countDtl.getRelationTaskId()==null){
            return null;
        }
        if (countDtl.getRelationTaskId().compareTo(BigDecimal.ZERO)==0){
            return null;
        }
        BigDecimal relationTaskId;
        BigDecimal zero=BigDecimal.ZERO;
        while (true){
            if (countDtl.getRelationTaskId()==null){
                return countDtl;
            }
            if (countDtl.getRelationTaskId().compareTo(zero)==0){
                return countDtl;
            }
            relationTaskId = countDtl.getRelationTaskId();
            countDtl = invCountDtlMapper.
                    selectOne(new QueryWrapper<InvCountDtl>().eq("INV_COUNT_DTL_ID", relationTaskId));
        }
    }

    //转换盘点范围
    public InvScopeDto searchScope(InvCountScope scope,Integer whsId,Boolean emptyFlag,Boolean putFlag) throws Exception{
        List<String> zoneCodes;
        List<String> locCodes;
        List<String> lotnoCodes=new ArrayList<>();
        List<String> cateCodes=new ArrayList<>();
        List<String> skuCodes=new ArrayList<>();

        if (scope.getArea().equals(STAR)){
            List<Zone> zones = invCountHeaderMapper.selectCoutnZones(whsId, null, null, emptyFlag);
            if (!CollectionUtil.isEmpty(zones)){
                zoneCodes = zones.stream().map(t -> t.getZoneCode()).collect(Collectors.toList());
            }else {
                zoneCodes=new ArrayList<>();
            }
        }else {
            zoneCodes=Arrays.asList(scope.getArea().split(","));
        }

        if (scope.getLoc().equals(STAR)){
            if (zoneCodes!=null&&zoneCodes.size()>0){
                List<Location> locations = invCountHeaderMapper.selectCoutnLocs(zoneCodes, null, null, emptyFlag);
                if (!CollectionUtil.isEmpty(locations)){
                    locCodes = locations.stream().map(t -> t.getLocCode()).collect(Collectors.toList());
                }else {
                    locCodes=new ArrayList<>();
                }
            }else {
                locCodes=new ArrayList<>();
            }
        }else {
            locCodes=Arrays.asList(scope.getLoc().split(","));
        }

        if (scope.getLotNo()!=null){
            if (scope.getLotNo().equals(STAR)){
                if (locCodes!=null&&locCodes.size()>0){
                    List<Lotno> lotnos = invCountHeaderMapper.selectCoutnLotnos(whsId, locCodes, null, null, emptyFlag, putFlag);
                    if (lotnos!=null&&lotnos.size()>0){
                        for (Lotno lotno : lotnos) {
                            if (lotno!=null){
                                if (lotno.getLotno()!=null){
                                    lotnoCodes.add(lotno.getLotno());
                                }
                            }
                        }
                    }
                }else {
                    List<Lotno> lotnos = invCountHeaderMapper.selectCoutnLotnosNew(whsId, locCodes, null, null, emptyFlag, putFlag);
                    if (lotnos!=null&&lotnos.size()>0){
                        for (Lotno lotno : lotnos) {
                            if (lotno!=null){
                                if (lotno.getLotno()!=null){
                                    lotnoCodes.add(lotno.getLotno());
                                }
                            }
                        }
                    }
                }
            }else {
                lotnoCodes=Arrays.asList(scope.getLotNo().split(","));
            }
        }


        if (scope.getSkuCategory().equals(STAR)){
            if (locCodes!=null&&locCodes.size()>0){
                List<SkuCate> catesList = invCountHeaderMapper.selectCoutnCates(whsId, locCodes, lotnoCodes, null, null, emptyFlag, putFlag);
                if (CollectionUtil.isEmpty(catesList)){
                    Shift.fatal("查无对应库存记录!");
                }
                cateCodes = catesList.stream().map(t -> t.getSkuCateCode()).collect(Collectors.toList());
            }else {
                List<SkuCate> catesList = invCountHeaderMapper.selectCoutnCatesNew(whsId, locCodes, lotnoCodes, null, null, emptyFlag, putFlag);
                if (CollectionUtil.isEmpty(catesList)){
                    Shift.fatal("查无对应库存记录!");
                }
                cateCodes = catesList.stream().map(t -> t.getSkuCateCode()).collect(Collectors.toList());
            }
        }else {
            cateCodes=Arrays.asList(scope.getSkuCategory().split(","));
        }


        if (scope.getSku().equals(STAR)){
            if (locCodes!=null&&locCodes.size()>0){
                skuCodes = invCountHeaderMapper.selectCoutnSku(whsId,locCodes,lotnoCodes,cateCodes, null, null, emptyFlag,putFlag)
                        .stream().map(t -> t.getSkuCode()).collect(Collectors.toList());
                if (CollectionUtil.isEmpty(skuCodes)){
                    Shift.fatal("查无对应库存记录!");
                }
            }else {
                skuCodes = invCountHeaderMapper.selectCoutnSkuNew(whsId,locCodes,lotnoCodes,cateCodes, null, null, emptyFlag,putFlag)
                        .stream().map(t -> t.getSkuCode()).collect(Collectors.toList());
                if (CollectionUtil.isEmpty(skuCodes)){
                    Shift.fatal("查无对应库存记录!");
                }
            }

        }else {
            skuCodes=Arrays.asList(scope.getSku().split(","));
            if (CollectionUtil.isEmpty(skuCodes)){
                Shift.fatal("查无对应库存记录!");
            }
        }

        List<Integer> locIds=new ArrayList<>();
        if (locCodes!=null&&locCodes.size()>0){
            locIds = locationMapper
                    .selectList(new QueryWrapper<Location>().in("LOC_CODE", locCodes)).
                            stream().map(t -> t.getLocId()).collect(Collectors.toList());
        }
        List<Integer> skuIds = skuMapper.selectList(new QueryWrapper<Sku>().in("SKU_CODE", skuCodes)).
                stream().map(t -> t.getSkuId()).collect(Collectors.toList());
        InvScopeDto dto=new InvScopeDto();
        dto.setLocIds(locIds);
        dto.setSkuIds(skuIds);
        dto.setLotnos(lotnoCodes);

        return dto;
    }


    public List<String> contverStar(List<String> codeList){
        if (CollectionUtil.isEmpty(codeList)){
            return codeList;
        }
        if (codeList.get(0).equals("-1")){
            return Arrays.asList(STAR);
        }
        return codeList;
    }

    //根据最后一次复盘任务ID查询复盘次数
    @Transactional(rollbackFor = Exception.class, propagation = Propagation.REQUIRED)
    public int searchReCountNumer(BigDecimal lastDtlId){
        BigDecimal zero = BigDecimal.ZERO;
        int i=0;
        if (lastDtlId==null){
            return i;
        }
        if (lastDtlId.equals(zero)){
            return i;
        }
        InvCountDtl countDtl = invCountDtlMapper.
                selectOne(new QueryWrapper<InvCountDtl>().eq("INV_COUNT_DTL_ID", lastDtlId));

        BigDecimal relationTaskId;
        if (countDtl==null) return i;
        while (true){
            if (countDtl.getRelationTaskId()==null||countDtl.getRelationTaskId().signum()==0){
                return i;
            }
            relationTaskId = countDtl.getRelationTaskId();
            countDtl = invCountDtlMapper.
                    selectOne(new QueryWrapper<InvCountDtl>().eq("INV_COUNT_DTL_ID", relationTaskId));
            i++;
        }

    }

}
